package container

import (
	"fmt"
	"os"
	"time"

	"cloudea.com/container/config"
	"cloudea.com/container/domain/image"
	"cloudea.com/container/utils"
)

/** 容器的构造函数 （工厂函数） */
func NewContainer(
	name string,
	image image.Image,
	status ContainerStatus,
	command []string,
	createdTime time.Time,
	threadId int,
	ip string) *Container {

	// 创建基础目录
	containerBase := config.GetContainerBase(name)
	containerBaseDiff := containerBase + "/diff"
	containerBaseWork := containerBase + "/work"
	containerBaseMerged := containerBase + "/merged"
	containerBaseMeta := containerBase + "/manifest.json"

	defer func() {
		err := recover()
		if err != nil {
			// 如果在创建过程中出现一些错误，那么则把已经创建的文件删除
			fmt.Printf("%v\n", err)
			os.RemoveAll(containerBase)
			return
		}
	}()

	// 如果存在就不用创建了
	if utils.FileExists(containerBaseMeta) {
		return nil
	}
	// 创建overlayfs2
	err := os.MkdirAll(containerBaseDiff, os.ModePerm)
	if err != nil {
		panic(err)
	}
	err = os.MkdirAll(containerBaseWork, os.ModePerm)
	if err != nil {
		panic(err)
	}
	err = os.MkdirAll(containerBaseMerged, os.ModePerm)
	if err != nil {
		panic(err)
	}

	// 创建软链接到镜像的目录下
	softLink := config.GetImageContainer(image.GetName(), image.GetTag(), name)
	utils.Assert(os.Symlink(containerBase, softLink))

	// 创建容器实例
	container := Container{
		Name:        name,
		Image:       image,
		Status:      status,
		CreatedTime: createdTime,
		ThreadId:    threadId,
		Command:     command,
		Ip:          ip,
		Hash:        GenHashCode(),
	}

	// 保存配置
	utils.Assert(REPOSITORY.Save(container))

	return &container
}
